/*
 * Copyright (C) 2012-2016 TeraCN
 * 
 * This file is part of TeraCN.
 * 
 * TeraCN is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 * 
 * TeraCN is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
 */
package tera.gameserver.model.playable;

import java.lang.reflect.Field;

import rlib.logging.Loggers;
import rlib.util.ReflectionUtils;
import rlib.util.VarTable;
import rlib.util.array.Array;
import rlib.util.pools.Foldable;
import rlib.util.pools.FoldablePool;
import rlib.util.pools.Pools;

/**
 * @author Ronn Mod Evestu
 */
public class Playerdetails2 implements Foldable, Cloneable
{
	private static final FoldablePool<Playerdetails2> pool = Pools.newConcurrentFoldablePool(Playerdetails2.class);
	
	/**
	 * Method getInstance.
	 * @param objectId int
	 * @return Playerdetails2
	 */
	public static final Playerdetails2 getInstance(int objectId)
	{
		Playerdetails2 detailsappearance = pool.take();
		
		if (detailsappearance == null)
		{
			detailsappearance = new Playerdetails2();
		}
		
		detailsappearance.setObjectId(objectId);
		return detailsappearance;
	}
	
	private int objectId;
	private int[] details2;
	
	/**
	 * Method getDetails2.
	 * @return int[]
	 */
	public int[] getDetails2()
	{
		return details2;
	}
	
	/**
	 * Method setDetails2.
	 * @param details2 int[]
	 */
	public void setDetails2(int[] details2)
	{
		this.details2 = details2;
	}
	
	/**
	 * Method getObjectId.
	 * @return int
	 */
	public final int getObjectId()
	{
		return objectId;
	}
	
	/**
	 * Method setObjectId.
	 * @param objectId int
	 */
	public final void setObjectId(int objectId)
	{
		this.objectId = objectId;
	}
	
	/**
	 * Method finalyze.
	 * @see rlib.util.pools.Foldable#finalyze()
	 */
	@Override
	public void finalyze()
	{
	}
	
	/**
	 * Method reinit.
	 * @see rlib.util.pools.Foldable#reinit()
	 */
	@Override
	public void reinit()
	{
	}
	
	public void fold()
	{
		pool.put(this);
	}
	
	/**
	 * Method toXML.
	 * @param detailsappearance Playerdetails2
	 * @param id String
	 * @return String
	 */
	public static String toXML(Playerdetails2 detailsappearance, String id)
	{
		final StringBuilder builder = new StringBuilder();
		builder.append("<detailsappearance id=\"").append(id).append("\" >\n");
		final Array<Field> fields = ReflectionUtils.getAllFields(detailsappearance.getClass(), Object.class, true, "pool", "objectId");
		
		try
		{
			for (Field field : fields)
			{
				final String name = field.getName();
				final boolean old = field.isAccessible();
				field.setAccessible(true);
				final String value = String.valueOf(field.get(detailsappearance));
				builder.append("	<set name=\"").append(name).append("\" value=\"").append(value).append("\" />").append("\n");
				field.setAccessible(old);
			}
		}
		catch (IllegalArgumentException | IllegalAccessException e)
		{
			Loggers.warning(detailsappearance.getClass(), e);
		}
		
		builder.append("</detailsappearance>");
		return builder.toString();
	}
	
	/**
	 * Method fromXML.
	 * @param <T>
	 * @param detailsappearance T
	 * @param vars VarTable
	 * @return T
	 */
	public static <T extends Playerdetails2> T fromXML(T detailsappearance, VarTable vars)
	{
		final Array<Field> fields = ReflectionUtils.getAllFields(detailsappearance.getClass(), Object.class, true, "pool", "objectId");
		
		try
		{
			for (Field field : fields)
			{
				final boolean old = field.isAccessible();
				field.setAccessible(true);
				field.setInt(detailsappearance, vars.getInteger(field.getName(), field.getInt(detailsappearance)));
				field.setAccessible(old);
			}
		}
		catch (IllegalArgumentException | IllegalAccessException e)
		{
			Loggers.warning(detailsappearance.getClass(), e);
		}
		
		return detailsappearance;
	}
	
	/**
	 * Method copy.
	 * @return Playerdetails2
	 */
	public Playerdetails2 copy()
	{
		try
		{
			return (Playerdetails2) clone();
		}
		catch (CloneNotSupportedException e)
		{
			return null;
		}
	}
}